17-3 おwd腄Gp妐う

資料庫可以包含數個資料表,不同資料表之間的欄位可以有關聯姓,我們可以根據這些資料欄位的關聯性來使資料庫的資料更符合實際世界的狀況,此種具有關聯性的資料庫,即稱為關聯性資料庫(Relational Databases)。

我們首先以 asp/example/database/song01.mdb 內的 song 資料表來說明,其內容如下:

序號 歌曲名稱 主唱者 年份
用心良苦 張宇 1993 
聽海 張惠妹 1998 
牽手 張惠妹 2001 
最熟悉的陌生人 蕭亞軒 2000 
戀人未滿 S.H.E 2002 
I.O.I.O. S.H.E 2002 
11 每次都想呼喊你的名字 永邦 2002 
12 最熟悉的陌生人 蕭亞軒 2000 
13 原來你什麼都不要 張惠妹 1999 
14 窗外的天氣 蕭亞軒 1999 
16 野百合也有春天 永邦 2002 

很明顯地,「主唱者」的欄位中,很多資料都是重複的,如果我們還要增加和「主唱者」相關的資料,例如「出道年份」、「身高」、「嗜好」等,就會增加更多重覆的資料,因此,我們可以將和主唱者相關的資料放到另一個資料表 singer,並指定每首歌曲(在 song 資料表)所對應的歌手(在 singer 資料表),這樣做的好處是:

為方便說明起見,我們使用一個資料較少的檔案 asp/example/database/song02.mdb 來進行以下說明,其中 song 資料表的內容如下:

序號 名稱 歌手序號 年份
用心良苦 1993 
聽海 1998 
戀人未滿 2002 
I.O.I.O. 2002 
17 神話 1983 
18 花心 1993 

singer 資料表的內容如下:

序號 姓名 類別 出道年份
張宇 男歌手 1973 
張惠妹 女歌手 1975 
蕭亞軒 女歌手 1971 
S.H.E 女團體 1960 
11 永邦 男歌手 1969 

由上述列表可以知道,每一首歌有一個欄位是「歌手序號」,指到 singer 資料表的「序號」欄位,就可以找到對應的歌手資料。我們可以使用 SQL 查詢來列出歌手和歌曲的所有可能組合,所用的 SQL 指令為:

SELECT song.名稱, singer.姓名 FROM song, singer; 所得到的結果是:

名稱 姓名
用心良苦 張宇 
聽海 張宇 
戀人未滿 張宇 
I.O.I.O. 張宇 
神話 張宇 
花心 張宇 
用心良苦 張惠妹 
聽海 張惠妹 
戀人未滿 張惠妹 
I.O.I.O. 張惠妹 
神話 張惠妹 
花心 張惠妹 
用心良苦 蕭亞軒 
聽海 蕭亞軒 
戀人未滿 蕭亞軒 
I.O.I.O. 蕭亞軒 
神話 蕭亞軒 
花心 蕭亞軒 
用心良苦 S.H.E 
聽海 S.H.E 
戀人未滿 S.H.E 
I.O.I.O. S.H.E 
神話 S.H.E 
花心 S.H.E 
用心良苦 永邦 
聽海 永邦 
戀人未滿 永邦 
I.O.I.O. 永邦 
神話 永邦 
花心 永邦 

這個列表共有 30 筆資料,代表由第一個資料表(6 筆資料)和第二個資料表(5 筆資料)的所有可能組合,但是我們並沒有用到兩個資料表之間的關聯,所以得到的結果當然不正確。我們可以把有關聯性的欄位(在此例是 song 資料表的「歌手序號」以及 singer 資料表的「序號」欄位)加入條件式,得到下列的 SQL 指令:

SELECT song.名稱, singer.姓名 FROM singer, song WHERE (song.歌手序號=singer.序號); 對應的「設計檢視」畫面是:

所得到的結果是:

名稱 姓名
用心良苦 張宇 
聽海 張惠妹 
戀人未滿 S.H.E 
I.O.I.O. S.H.E 

上述的做法是以 where 子句來指定資料所必須具備的特性,另一種做法則是直接在「設計檢視」中指定資料表之間的關聯,我們可先將 song 和 singer 資料表加入「設計檢視」的查詢,然後選取 song 資料表的「歌手序號」欄位後,拖放到 singer 資料表的「序號」欄位,就可以建立這兩個資料表的關聯性(會產生關聯線段以連接有關聯性的欄位),然後再加入需要查詢的欄位名稱,顯示畫面如下:

對應的 SQL 指令如下: SELECT song.序號, song.名稱, singer.姓名 FROM song INNER JOIN singer ON song.歌手序號 = singer.序號; 所得到的結果是:

序號 名稱 姓名
用心良苦 張宇 
聽海 張惠妹 
戀人未滿 S.H.E 
I.O.I.O. S.H.E 

在上述範例中,SQL 指令使用了 INNER JOIN。事實上,對於資料表的連接(Join),可以分成三類:

  1. Inner Join:只會列出來兩個資料表連接欄位的資料相同的記錄。
  2. Left Join:列出所有來自左資料表的記錄,以及連接欄位相等的右資料表的記錄
  3. Right Join:列出所有來自右資料表的記錄,以及連接欄位相等的左資料表的記錄
文字說明事實上不容易瞭解,讓我們來看看範例。如果我們雙擊連接關聯性欄位的線段,就會跳出「連接屬性」的視窗,如下:

此視窗的預設值就是「僅包含兩個資料表連接欄位的資料相同的記錄」,這就是 Inner Join。如果我們點選第 2個選項(「包括所有來自'song'的記錄和只包括那些連接欄位相等的'singer'欄位」),這就是 Left Join,按「確定」之後,查詢畫面如下:

其中關聯線段被加上了一個由左向右的箭頭,代表 Left Join,相對應的 SQL 命令如下: 對應的 SQL 指令如下: SELECT song.序號, song.名稱, singer.姓名 FROM song LEFT JOIN singer ON song.歌手序號 = singer.序號; 所得到的結果是:

序號 名稱 姓名
用心良苦 張宇 
聽海 張惠妹 
戀人未滿 S.H.E 
I.O.I.O. S.H.E 
17 神話 null 
18 花心 null 

此結果代表「列出所有的歌,以及這些歌所可能對應的歌手」。

Hint
「null」代表沒有資料存在。

如果我們點選第 3 個選項(「包括所有來自'singer'的記錄和只包括那些連接欄位相等的'song'欄位」),這就是 Right Join,對應的 SQL 命令如下:

SELECT song.序號, song.名稱, singer.姓名 FROM song RIGHT JOIN singer ON song.歌手序號 = singer.序號; 所得到的結果是:

序號 名稱 姓名
用心良苦 張宇 
聽海 張惠妹 
null null 蕭亞軒 
I.O.I.O. S.H.E 
戀人未滿 S.H.E 
null null 永邦 

此結果代表「列出所有的歌手,以及這些歌手所可能對應的歌」。

Hint
有關於 Outer Join,說明如下:
  • Left Join 又稱為 Left Outer Join;Right Join 又稱為 Right Outer Join。
  • Full Outer Join 就是 Left Join 和 Right Join 的聯集,但是 Access 目前並不支援。

以上的做法,是在建立查詢時,才建立起資料表之間的關聯,另一個方式,則是事先就建立好資料表的關聯,這是永久性的關聯,所以在進行查詢時,也會將此關聯包含進來。以資料庫 song02.mdb 為例,我們可以開啟「資料庫工具/資料庫關聯圖」,看到的畫面如下:

我們可以選取 song 資料表的「歌手序號」欄位後,拖放到 singer 資料表的「序號」欄位,就可以建立這兩個資料表的永久關聯,此時會跳出來「編輯關聯」的畫面,如下:

有關這個畫面的選項「強迫參考完整性」,我們會在下一節說明。目前你只要按下「建立」,即可建立根基於 Inner Join 的永久關聯,你也可以按下「連接類型」,來設定其他類別的 Join,如 Left Join 或是 Right Join。此新建立的關聯,會在「資料庫關聯圖」以線段的方式顯示出來,此線段所連結的欄位即是互有關聯的欄位,畫面如下:

若要編輯關聯,可以雙擊此線段,即可開啟「編輯關聯」的視窗。

一旦建立永久關聯後,在「設計檢視」模式下編輯查詢時,只要加入相關的資料表,即可反應此永久關聯,而不需要再自行手動加入。


JScript 程式設計與應用:用於伺服器端的 ASP 環境